'use strict'

import axios from 'axios'
import store from '@/store'
import router from '@/router'
import { getAllPromise } from '@/utils/tools'
import { objKeySort, dateChange } from '@/filters'
import { Toast } from 'vant'
import md5 from 'js-md5'
import { getCookie } from '@/utils/cookie'
// 完整配置参考:  https://github.com/axios/axios#request-config
axios.defaults.headers.post['Content-Type'] = 'application/json;charset=utf-8'

let config = {
  baseURL: process.env.BASE_URL || process.env.VUE_APP_DEMO_URL || '',
  timeout: 60 * 1000,
  withCredentials: false,
  crossDomain: true
}

const _axios = axios.create(config)

// 注册all方法，执行多个并发请求
// 可传入Promise、包含Promise的数组、返回值为Promise的方法
_axios.all = (...requsets) => {
  // 获取所有Promise对象
  let promiseList = getAllPromise(requsets)
  return new Promise((resolve, reject) => {
    axios
      .all(promiseList)
      .then(
        axios.spread((...response) => {
          // 两个请求现在都执行完成
          resolve(response)
        })
      )
      .catch(error => {
        reject(error)
      })
  })
}

_axios.interceptors.request.use(
  config => {
    if (config.url.includes('api/sys/file')) {
      // 上传图片请求，不带请求头参数
    } else {
      let paramsNew = ''
      if (config.method === 'get' && config.params) {
        paramsNew = objKeySort(config.params)
      } else if (config.method === 'post' && config.data) {
        paramsNew = objKeySort(config.data)
      }
      config.headers.common['Content-Type'] = 'application/json;charset=utf-8'
      config.headers.common['Access-Control-Allow-Origin'] = '*'
      config.headers.common['userSig'] = 'userSig'
      config.headers.common['clientType'] = 'h5'
      config.headers.common['timestamp'] = dateChange()
      config.headers.common['sign'] = md5(encodeURIComponent(paramsNew + config.headers.common.clientType + config.headers.common.timestamp + 'n8R7vPaF3nJc'))
      config.headers.common['Authorization'] = getCookie('token')
    }
    return config
  },
  error => {
    return Promise.reject(error)
  }
)

// 拦截响应
_axios.interceptors.response.use(
  response => {
    // 用来判断是否请求成功
    const success = response.status === 200
    let message = ''
    if (!success) {
      if (typeof response.data === 'string') {
        message = '服务器错误，未获取到响应数据'
      } else {
        if (response.status === 200 && response.data.code === 0) {
          return Promise.reject(response)
        }
        // 请求成功，但在业务上为失败
        message = response.data.message || response.data.errorData || '操作执行失败'
      }
      Toast(message)
      return Promise.reject(response)
    }
    return {
      data: response.data,
      success,
      message
    }
  },
  error => {
    let message = ''
    if (!navigator.onLine) {
      message = '网络连接异常，请检查网络'
      Toast(message)
      return Promise.reject(error)
    }
    if (!error.response) {
      message = '连接服务器失败'
      Toast(message)
      return Promise.reject(error)
    }
    let status = error.response.status
    if (status === 401) {
      message = '您已在其他地方登录'
      store.dispatch('logout')
      Toast(message)
      return Promise.reject(error)
    }
    if (status === 412) {
      message = '登录过期,重新登录'
      Toast(message)
      router.push({ name: 'home' })
      window.location.reload()
      return Promise.reject(error)
    }
    if (status < 200) {
      message = `未处理的消息响应，状态码：${status}`
    } else if (status >= 300 && status < 400) {
      message = `未处理的重定向响应，状态码：${status}`
    } else if (status === 406) {
      message = '已经参加过该考试'
      window.history.back()
    } else if (status >= 400 && status < 500) {
      message = `客户端错误，状态码：${status}`
    } else if (status >= 500) {
      message = `服务器错误，状态码：${status}`
    }
    Toast(message)
    // 系统请求失败
    return Promise.reject(error)
  }
)

export default _axios
